<template>
  <div class="app-container p-6">
    <!-- 页面标题和操作按钮 - 完全匹配原型 -->
    <div class="page-header-section flex flex-col md:flex-row md:items-center md:justify-between mb-6">
      <div class="page-title-area">
        <h1 class="text-2xl font-bold text-text-primary">用户管理</h1>
        <p class="text-text-muted mt-2">管理系统中的所有用户，包括创建、编辑、删除和分配角色</p>
      </div>
      <div class="page-actions-area mt-4 md:mt-0">
        <!-- 主要操作按钮 -->
        <button
          @click="handleAdd"
          v-permission="'user:create'"
          class="primary-action-btn bg-primary hover:bg-primary-hover text-white px-6 py-2 rounded-md flex items-center shadow-card transition-all"
        >
          <i class="fas fa-plus mr-2"></i>
          <span>新增用户</span>
        </button>

        <!-- 次要操作按钮组 -->
<!--        <div class="secondary-actions-group mt-3 md:mt-2 flex flex-wrap gap-2">-->
<!--          <button-->
<!--            @click="handleResetAdmin"-->
<!--            v-permission="'user:reset-password'"-->
<!--            class="secondary-action-btn px-4 py-1.5 border border-border rounded-md text-text-secondary hover:bg-bg-hover hover:text-text-primary transition-colors flex items-center text-sm"-->
<!--          >-->
<!--            <i class="fas fa-key mr-1.5"></i>-->
<!--            <span>重置管理员密码</span>-->
<!--          </button>-->
<!--        </div>-->
      </div>
    </div>

    <!-- 搜索和筛选区域 - 完全匹配原型样式 -->
    <div class="search-form-card bg-panel rounded-lg shadow-card p-6 mb-6">
      <div class="grid grid-cols-1 md:grid-cols-3 gap-6">
        <!-- 用户名搜索 -->
        <div>
          <label class="block text-text-secondary mb-2 text-sm font-medium">用户名</label>
          <div class="relative">
            <input
              type="text"
              v-model="queryParams.username"
              placeholder="请输入用户名"
              class="search-input pl-10 pr-4 py-2 w-full rounded-md border border-border bg-bg-hover focus:outline-none focus:ring-2 focus:ring-primary/30 focus:border-primary"
            >
            <i class="fas fa-search absolute left-3 top-1/2 transform -translate-y-1/2 text-text-muted"></i>
          </div>
        </div>

        <!-- 邮箱搜索 -->
        <div>
          <label class="block text-text-secondary mb-2 text-sm font-medium">邮箱</label>
          <div class="relative">
            <input
              type="text"
              v-model="queryParams.email"
              placeholder="请输入邮箱"
              class="search-input pl-10 pr-4 py-2 w-full rounded-md border border-border bg-bg-hover focus:outline-none focus:ring-2 focus:ring-primary/30 focus:border-primary"
            >
            <i class="fas fa-envelope absolute left-3 top-1/2 transform -translate-y-1/2 text-text-muted"></i>
          </div>
        </div>

        <!-- 状态筛选 -->
        <div>
          <label class="block text-text-secondary mb-2 text-sm font-medium">状态</label>
          <div class="search-select-wrapper">
            <el-select
              v-model="queryParams.status"
              placeholder="全部状态"
              clearable
              class="search-select w-full"
            >
              <el-option label="启用" :value="1" />
              <el-option label="禁用" :value="0" />
            </el-select>
          </div>
        </div>
      </div>

      <!-- 高级搜索和操作按钮 -->
      <div class="mt-4 flex justify-between items-center">
        <button class="text-primary hover:text-primary-hover text-sm transition-colors">
          <i class="fas fa-sliders-h mr-1"></i>
          高级搜索
        </button>

        <!-- 操作按钮组 -->
        <div class="flex space-x-3">
          <button
            @click="resetQuery"
            class="px-4 py-2 border border-border rounded-md text-text-secondary hover:bg-bg-hover transition-colors"
          >
            重置
          </button>
          <button
            @click="handleQuery"
            class="px-4 py-2 bg-primary text-white rounded-md hover:bg-primary-hover shadow-sm transition-colors"
          >
            搜索
          </button>
        </div>
      </div>
    </div>

    <!-- 批量操作工具栏 -->
    <div v-if="selectedUsers.length > 0" class="bg-panel radius-lg p-4 mb-4">
        <div class="d-flex items-center justify-between">
          <div class="d-flex items-center">
            <span class="mr-4 text-primary">已选择 {{ selectedUsers.length }} 个用户</span>
            <el-button-group>
              <el-button
                type="success"
                size="small"
                :icon="Plus"
                @click="handleBatchEnable"
                v-permission="'user:update'"
              >
                批量启用
              </el-button>
              <el-button
                type="warning"
                size="small"
                @click="handleBatchDisable"
                v-permission="'user:update'"
              >
                批量禁用
              </el-button>
              <el-button
                type="danger"
                size="small"
                :icon="Delete"
                @click="handleBatchDelete"
                v-permission="'user:delete'"
              >
                批量删除
              </el-button>
            </el-button-group>
          </div>
        <el-button size="small" @click="clearSelection">取消选择</el-button>
      </div>
    </div>

    <SystemTable
      title="用户列表"
      :total="total"
      @page-change="handlePageChange"
      @filter="handleTableFilter"
      @import="handleImport"
      @export="handleExport"
      import-permission="user:import"
      export-permission="user:export"
      v-loading="loading"
      :data="userList"
      row-key="userId"
      ref="tableRef"
      @selection-change="handleSelectionChange"
    >
      <el-table-column type="selection" width="55" />
      <el-table-column prop="username" label="用户名" show-overflow-tooltip>
        <template #default="{ row }">
          <div class="username-cell">
            <img
              :src="row.avatarUrl || `https://api.dicebear.com/7.x/initials/svg?seed=${row.nickname || row.username}`"
              :alt="`${row.nickname || row.username}的头像`"
              class="user-avatar-small"
              @error="handleAvatarError"
            >
            <span class="username-text">{{ row.username }}</span>
          </div>
        </template>
      </el-table-column>
      <el-table-column prop="nickname" label="昵称" show-overflow-tooltip align="left" />
      <el-table-column prop="email" label="邮箱" show-overflow-tooltip align="left" />
      <el-table-column prop="phone" label="手机号" show-overflow-tooltip align="center" />
      <el-table-column label="角色" show-overflow-tooltip align="left">
        <template #default="{ row }">
          <div v-if="row.roles && row.roles.length > 0" class="role-tags">
            <el-tag
              v-for="role in row.roles.slice(0, 2)"
              :key="role.roleId || role.id"
              type="info"
              size="small"
              class="mr-1 mb-1"
            >
              {{ role.roleName || role.name }}
            </el-tag>
            <el-tag v-if="row.roles.length > 2" type="info" size="small" class="mr-1 mb-1">
              +{{ row.roles.length - 2 }}
            </el-tag>
          </div>
          <span v-else style="color: var(--text-muted);">未分配角色</span>
        </template>
      </el-table-column>
      <el-table-column prop="createTime" label="创建时间" sortable show-overflow-tooltip align="left" />
      <el-table-column label="状态" width="80" align="center">
        <template #default="{ row }">
          <span
            class="status-tag"
            :class="row.status === 1 ? 'status-enabled' : 'status-disabled'"
          >
            {{ row.status === 1 ? '启用' : '禁用' }}
          </span>
        </template>
      </el-table-column>
      <el-table-column label="封禁状态" width="100" align="center">
        <template #default="{ row }">
          <el-tag v-if="row.isBanned" type="danger" size="small">
            已封禁
          </el-tag>
          <el-tag v-else type="success" size="small">
            正常
          </el-tag>
        </template>
      </el-table-column>
      <el-table-column label="操作" fixed="right" align="center" width="240">
        <template #default="{ row }">
          <div class="table-actions">
            <button
              class="action-btn edit-btn"
              @click="handleEdit(row)"
              v-permission="'user:update'"
              title="编辑"
            >
              <i class="fas fa-edit"></i>
            </button>
            <button
              class="action-btn view-btn"
              @click="handleAssignRole(row)"
              v-permission="'user:assign-role'"
              title="分配角色"
            >
              <i class="fas fa-user-shield"></i>
            </button>
            <button
              v-if="!row.isBanned"
              class="action-btn ban-btn"
              @click="handleBan(row)"
              v-permission="'auth:user:ban'"
              title="封禁"
            >
              <i class="fas fa-ban"></i>
            </button>
            <button
              v-else
              class="action-btn unban-btn"
              @click="handleUnban(row)"
              v-permission="'auth:user:ban'"
              title="解封"
            >
              <i class="fas fa-unlock"></i>
            </button>
            <button
              class="action-btn delete-btn"
              @click="handleDelete(row)"
              v-permission="'user:delete'"
              title="删除"
            >
              <i class="fas fa-trash"></i>
            </button>
          </div>
        </template>
      </el-table-column>
    </SystemTable>

  <!-- 新增/编辑用户对话框 -->
  <el-dialog
    v-model="formVisible"
    :title="isEdit ? '编辑用户' : '新增用户'"
    width="600px"
    destroy-on-close
  >
    <el-form
      ref="userFormRef"
      :model="formData"
      :rules="formRules"
      label-width="80px"
    >
      <el-form-item label="用户名" prop="username">
        <el-input
          v-model="formData.username"
          placeholder="请输入用户名"
          :disabled="isEdit"
        />
      </el-form-item>

      <el-form-item label="密码" prop="password" v-if="!isEdit">
        <el-input
          v-model="formData.password"
          type="password"
          placeholder="请输入密码"
          show-password
        />
      </el-form-item>

      <el-form-item label="昵称" prop="nickname">
        <el-input
          v-model="formData.nickname"
          placeholder="请输入昵称"
        />
      </el-form-item>

      <el-form-item label="邮箱" prop="email">
        <el-input
          v-model="formData.email"
          placeholder="请输入邮箱"
        />
      </el-form-item>

      <el-form-item label="手机号" prop="phone">
        <el-input
          v-model="formData.phone"
          placeholder="请输入手机号"
        />
      </el-form-item>

      <el-form-item label="头像">
        <div class="avatar-uploader">
          <el-avatar
            :size="72"
            :src="avatarPreview || defaultAvatar"
            shape="circle"
          />
          <el-upload
            class="ml-3"
            :auto-upload="false"
            :show-file-list="false"
            :on-change="onAvatarChange"
            :before-upload="beforeAvatarUpload"
            accept="image/*"
          >
            <el-button type="primary" :icon="Upload">选择头像</el-button>
          </el-upload>
          <div v-if="formData.avatarUrl" class="text-muted mt-1" style="font-size:12px;">
            已上传
          </div>
        </div>
      </el-form-item>

      <el-form-item label="状态" prop="status">
        <el-radio-group v-model="formData.status">
          <el-radio :label="1">启用</el-radio>
          <el-radio :label="0">禁用</el-radio>
        </el-radio-group>
      </el-form-item>
    </el-form>

    <template #footer>
      <div class="dialog-footer">
        <el-button @click="handleCancel">取消</el-button>
        <el-button type="primary" @click="handleSubmit" :loading="loading">
          确定
        </el-button>
      </div>
    </template>
  </el-dialog>

  <!-- 分配角色对话框 -->
  <el-dialog
    v-model="roleDialogVisible"
    title="分配角色"
    width="600px"
    destroy-on-close
  >
    <div class="mb-4">
      <div class="text-sm text-gray-600 mb-2">
        为用户 <strong>{{ currentUser?.username }}</strong> 分配角色
      </div>
    </div>

    <!-- 角色选择区域 -->
    <div class="role-selection">
      <div class="mb-4">
        <div class="flex justify-between items-center mb-3">
          <h4 class="text-base font-medium">可选角色</h4>
          <div>
            <el-button size="small" @click="selectAllRoles">全选</el-button>
            <el-button size="small" @click="clearAllRoles">清空</el-button>
          </div>
        </div>

        <div class="border rounded-lg p-4 max-h-60 overflow-y-auto">
          <el-checkbox-group v-model="selectedRoleIds" class="role-checkbox-group">
            <div v-for="role in availableRoles" :key="role.roleId || role.id" class="role-item">
              <el-checkbox
                :label="role.roleId || role.id"
                class="role-checkbox"
              >
                <div class="role-info">
                  <div class="role-name">{{ role.roleName || role.name }}</div>
                  <div class="role-description" v-if="role.description">
                    {{ role.description }}
                  </div>
                </div>
              </el-checkbox>
            </div>
          </el-checkbox-group>
        </div>
      </div>

      <!-- 已选择的角色 -->
      <div class="mb-4" v-if="selectedRoleIds.length > 0">
        <h4 class="text-base font-medium mb-3">已选择的角色 ({{ selectedRoleIds.length }})</h4>
        <div class="selected-roles">
          <el-tag
            v-for="roleId in selectedRoleIds"
            :key="roleId"
            closable
            @close="removeRole(roleId)"
            class="mr-2 mb-2"
          >
            {{ getRoleName(roleId) }}
          </el-tag>
        </div>
      </div>
    </div>

    <template #footer>
      <div class="dialog-footer">
        <el-button @click="roleDialogVisible = false">取消</el-button>
        <el-button type="primary" @click="handleSaveRoles" :loading="roleLoading">
          保存
        </el-button>
      </div>
    </template>
  </el-dialog>

  <!-- 导入用户对话框 -->
  <el-dialog
    v-model="importDialogVisible"
    title="导入用户"
    width="500px"
  >
    <div>
      <el-alert
        title="温馨提示"
        type="info"
        :closable="false"
        class="mb-4"
      >
        <template #default>
          <div class="text-sm">
            <p>1. 请先下载导入模板，按照模板格式填写用户数据</p>
            <p>2. 用户名为必填项，且不能重复</p>
            <p>3. 真实姓名为必填项</p>
            <p>4. 支持xlsx格式文件</p>
          </div>
        </template>
      </el-alert>

      <el-button @click="handleDownloadTemplate" class="mb-4" type="primary" plain>
        <i class="fas fa-download mr-2"></i>
        下载导入模板
      </el-button>

      <el-upload
        class="upload-demo"
        drag
        :auto-upload="false"
        :on-change="handleFileChange"
        :limit="1"
        accept=".xlsx,.xls"
      >
        <i class="el-icon-upload"></i>
        <div class="el-upload__text">
          将文件拖到此处，或<em>点击选择文件</em>
        </div>
        <template #tip>
          <div class="el-upload__tip">
            只能上传 xlsx/xls 文件
          </div>
        </template>
      </el-upload>

      <el-checkbox v-model="updateSupport" class="mt-4">
        是否更新已存在的用户数据
      </el-checkbox>
    </div>

    <template #footer>
      <el-button @click="importDialogVisible = false">取消</el-button>
      <el-button type="primary" @click="handleImportConfirm" :loading="importLoading">
        开始导入
      </el-button>
    </template>
  </el-dialog>
  </div>
</template>

<script setup lang="ts">
import { ref, reactive, onMounted, nextTick } from 'vue'
import type { FormRules } from 'element-plus'
import { ElMessage, ElMessageBox } from 'element-plus'
import { Plus, Download, Upload, Search, Refresh, Edit, Delete, Key, UserFilled } from '@element-plus/icons-vue'
import { userApi, userRoleApi, exportUsersWithUI, importUsersWithUI, downloadUserTemplateWithUI } from '@/api/user'
import { useUserStore } from '@/stores/user'
import { roleApi } from '@/api/role'
import type { UserDTO, RoleDTO } from '@/types/api'
import request from '@/utils/request'
import { validateFileType, validateFileSize, FILE_TYPE_PRESETS } from '@/utils/upload'
import defaultAvatar from '@/assets/images/default-avatar.png'
import SystemTable from '@/components/SystemTable/index.vue'

// 响应式数据
const loading = ref(false)
const userList = ref<UserDTO[]>([])
const total = ref(0)
const selectedUsers = ref<UserDTO[]>([])
const tableRef = ref()

// 当前登录用户store（用于在编辑当前用户时同步头像到全局）
const userStore = useUserStore()

// 表单相关
const formVisible = ref(false)
const isEdit = ref(false)
const userFormRef = ref<any>()

// 角色分配相关
const roleDialogVisible = ref(false)
const roleLoading = ref(false)
const currentUser = ref<UserDTO | null>(null)
const availableRoles = ref<RoleDTO[]>([])
const selectedRoleIds = ref<string[]>([])
const userCurrentRoles = ref<string[]>([])

// 表单数据
const formData = reactive({
  userId: '',
  username: '',
  password: '',
  nickname: '',
  email: '',
  phone: '',
  status: 1,
  roles: [] as string[],
  avatarUrl: ''
})

const avatarPreview = ref<string>('')

const queryParams = reactive({
  current: 1,
  size: 10,
  username: '',
  email: '',  // 新增邮箱查询字段
  status: undefined as number | undefined
})

// 方法
const getList = async () => {
  loading.value = true
  try {
    const response = await userApi.queryUsers(queryParams)
    userList.value = response.data.data
    total.value = response.data.total
    
    // 检查每个用户的封禁状态
    // 注意：这需要后端提供封禁状态检查接口，或在用户列表中返回封禁状态
    // 当前简单判断：status=0 表示可能被封禁
    userList.value.forEach((user: any) => {
      user.isBanned = user.status === 0
    })
  } catch (error) {
    ElMessage.error('获取用户列表失败')
  } finally {
    loading.value = false
  }
}

const handleQuery = () => {
  queryParams.current = 1
  getList()
}

const resetQuery = () => {
  queryParams.username = ''
  queryParams.email = ''
  queryParams.status = undefined
  queryParams.current = 1
  getList()
}

// 简化的分页处理
const handlePageChange = (page: number, pageSize: number) => {
  queryParams.current = page
  queryParams.size = pageSize
  getList()
}

// SystemTable 事件处理
const handleTableFilter = () => {
  console.log('筛选功能')
  // 这里可以实现高级筛选功能
}

const handleAdd = () => {
  formVisible.value = true
  isEdit.value = false
  nextTick(() => {
    if (userFormRef.value) {
      userFormRef.value.resetFields()
    }
  })
  // 重置表单数据
  Object.assign(formData, {
    username: '',
    password: '',
    nickname: '',
    email: '',
    phone: '',
    status: 1,
    roles: [],
    avatarUrl: ''
  })
  avatarPreview.value = ''
}

const handleEdit = (row: UserDTO) => {
  formVisible.value = true
  isEdit.value = true
  nextTick(() => {
    if (userFormRef.value) {
      userFormRef.value.resetFields()
    }
  })
  // 填充表单数据
  Object.assign(formData, {
    userId: row.userId,
    username: row.username,
    nickname: row.nickname || '',
    email: row.email || '',
    phone: row.phone || '',
    status: row.status,
    roles: ((row as any).roles?.map((r: any) => r.roleId)) || [],
    avatarUrl: (row as any).avatarUrl || ''
  })
  avatarPreview.value = (row as any).avatarUrl || ''
}

const handleDelete = async (row: UserDTO) => {
  try {
    await ElMessageBox.confirm(
      `确定要删除用户"${row.username}"吗？`,
      '提示',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )

    await userApi.deleteUser(row.userId!)
    ElMessage.success('删除成功')
    getList()
  } catch (error) {
    if (error !== 'cancel') {
      ElMessage.error('删除失败')
    }
  }
}

const handleBan = async (row: UserDTO) => {
  try {
    // 第一步：确认封禁
    await ElMessageBox.confirm(
      `确定要封禁用户 "${row.username}" 吗？封禁后用户将被强制下线且无法登录。`,
      '封禁用户',
      {
        confirmButtonText: '确定封禁',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )
    
    // 第二步：输入封禁原因
    const { value: reason } = await ElMessageBox.prompt(
      '请输入封禁原因（将记录在日志中）：',
      '封禁原因',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        inputPlaceholder: '例如：违反使用规定',
        inputValue: '违反使用规定'
      }
    )
    
    // 执行封禁（-1表示永久封禁）
    await authApi.banUser(row.userId!, reason || '违反使用规定', -1)
    ElMessage.success('用户已永久封禁')
    getList()
  } catch (error) {
    if (error !== 'cancel' && error !== 'close') {
      ElMessage.error('封禁用户失败')
    }
  }
}

const handleUnban = async (row: UserDTO) => {
  try {
    await ElMessageBox.confirm(
      `确定要解除用户 "${row.username}" 的封禁吗？解封后用户可以正常登录。`,
      '解除封禁',
      {
        confirmButtonText: '确定解封',
        cancelButtonText: '取消',
        type: 'info'
      }
    )
    
    await authApi.unbanUser(row.userId!)
    ElMessage.success('用户已解封')
    getList()
  } catch (error) {
    if (error !== 'cancel') {
      ElMessage.error('解封用户失败')
    }
  }
}

const handleResetPassword = async (row: UserDTO) => {
  try {
    await ElMessageBox.confirm(
      `确定要重置用户"${row.username}"的密码吗？`,
      '提示',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )
    await userApi.resetUserPassword(row.userId!)
    ElMessage.success('密码已重置为默认密码')
  } catch (error) {
    if (error !== 'cancel') {
      ElMessage.error('重置密码失败')
    }
  }
}

const handleResetAdmin = async () => {
  try {
    await ElMessageBox.confirm(
      '确定要重置管理员(admin)密码为默认密码吗？',
      '提示',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )
    // 查询 admin 用户，获取其 userId 再调用重置接口
    const resp = await userApi.queryUsers({ current: 1, size: 1, username: 'admin' } as any)
    const adminUser = Array.isArray(resp.data?.data) ? resp.data.data[0] : null
    if (!adminUser?.userId) {
      throw new Error('未找到用户名为 admin 的用户')
    }
    await userApi.resetUserPassword(adminUser.userId)
    ElMessage.success('管理员密码已重置为默认密码')
    getList()
  } catch (error) {
    if (error !== 'cancel') {
      ElMessage.error((error as any)?.message || '重置管理员密码失败')
    }
  }
}

const handleExport = async () => {
  // 直接调用封装好的API函数
  await exportUsersWithUI({
    username: queryParams.username,
    email: queryParams.email,
    status: queryParams.status
  })
}

// 导入相关状态
const importDialogVisible = ref(false)
const importFile = ref<File | null>(null)
const updateSupport = ref(false)
const importLoading = ref(false)

const handleImport = () => {
  importDialogVisible.value = true
  importFile.value = null
  updateSupport.value = false
}

const handleFileChange = (file: any) => {
  importFile.value = file.raw
}

const handleImportConfirm = async () => {
  importLoading.value = true
  try {
    // 直接调用封装好的API函数，传入成功回调
    await importUsersWithUI(importFile.value, updateSupport.value, () => {
      importDialogVisible.value = false
      getList() // 刷新列表
    })
  } finally {
    importLoading.value = false
  }
}

const handleDownloadTemplate = async () => {
  // 直接调用封装好的API函数
  await downloadUserTemplateWithUI()
}

// 表格选择相关
const handleSelectionChange = (selection: UserDTO[]) => {
  selectedUsers.value = selection
}

const clearSelection = () => {
  tableRef.value?.clearSelection()
  selectedUsers.value = []
}

// 批量操作方法
const handleBatchDelete = async () => {
  if (selectedUsers.value.length === 0) {
    ElMessage.warning('请选择要删除的用户')
    return
  }

  try {
    await ElMessageBox.confirm(
      `确定要删除选中的 ${selectedUsers.value.length} 个用户吗？`,
      '批量删除确认',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )

    const userIds = selectedUsers.value.map(user => user.userId!).filter(id => id)
    await userApi.batchDeleteUsers(userIds)

    ElMessage.success(`成功删除 ${userIds.length} 个用户`)
    clearSelection()
    getList()

  } catch (error) {
    if (error !== 'cancel') {
      console.error('批量删除失败:', error)
      ElMessage.error('批量删除失败')
    }
  }
}

const handleBatchEnable = async () => {
  if (selectedUsers.value.length === 0) {
    ElMessage.warning('请选择要启用的用户')
    return
  }

  try {
    await ElMessageBox.confirm(
      `确定要启用选中的 ${selectedUsers.value.length} 个用户吗？`,
      '批量启用确认',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'info'
      }
    )

    const userIds = selectedUsers.value.map(user => user.userId!).filter(id => id)
    await userApi.batchEnableUsers(userIds)

    ElMessage.success(`成功启用 ${userIds.length} 个用户`)
    clearSelection()
    getList()

  } catch (error) {
    if (error !== 'cancel') {
      console.error('批量启用失败:', error)
      ElMessage.error('批量启用失败')
    }
  }
}

const handleBatchDisable = async () => {
  if (selectedUsers.value.length === 0) {
    ElMessage.warning('请选择要禁用的用户')
    return
  }

  try {
    await ElMessageBox.confirm(
      `确定要禁用选中的 ${selectedUsers.value.length} 个用户吗？`,
      '批量禁用确认',
      {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning'
      }
    )

    const userIds = selectedUsers.value.map(user => user.userId!).filter(id => id)
    await userApi.batchDisableUsers(userIds)

    ElMessage.success(`成功禁用 ${userIds.length} 个用户`)
    clearSelection()
    getList()

  } catch (error) {
    if (error !== 'cancel') {
      console.error('批量禁用失败:', error)
      ElMessage.error('批量禁用失败')
    }
  }
}

// 表单提交
const handleSubmit = async () => {
  try {
    if (!userFormRef.value) return
    await userFormRef.value.validate()

    loading.value = true

    // 将选中的角色ID放入后端接受的 roleIds 字段，避免把字符串数组绑定到 roles(List<RoleInfo>)
    const payload: any = {
      ...formData,
      roleIds: [...formData.roles],
      roles: undefined
    }
    if (isEdit.value) {
      // 编辑用户：不传密码
      payload.password = undefined
      await userApi.updateUser(formData.userId, payload)
      ElMessage.success('用户更新成功')
      // 如果编辑的是当前登录用户，且头像有变更，则同步更新到全局store，确保导航栏和个人中心立即生效
      if (formData.userId && userStore.userInfo?.userId === formData.userId) {
        if (formData.avatarUrl) {
          userStore.updateAvatar(formData.avatarUrl)
        } else {
          // 无头像字段变更时，尝试刷新一次用户信息
          try { await userStore.getUserInfo() } catch {}
        }
      }
    } else {
      // 新增用户
      await userApi.createUser(payload)
      ElMessage.success('用户创建成功')
    }

    formVisible.value = false
    getList()
  } catch (error: any) {
    console.error('保存用户失败:', error)
    ElMessage.error(error?.message || '保存失败')
  } finally {
    loading.value = false
  }
}

// 头像上传相关
const beforeAvatarUpload = (file: File) => {
  if (!validateFileType(file, FILE_TYPE_PRESETS.image)) return false
  if (!validateFileSize(file, { maxSize: 5 })) return false
  // 去掉尺寸/宽度限制，仅校验类型与大小
  return true
}

const onAvatarChange = async (file: any) => {
  try {
    const raw: File = file.raw || file
    const ok = await beforeAvatarUpload(raw)
    if (!ok) return
    // 本地预览
    avatarPreview.value = URL.createObjectURL(raw)
    // 上传到文件服务
    const fd = new FormData()
    fd.append('file', raw)
    fd.append('businessType', 'avatar')
    fd.append('isPublic', 'true')
    const resp = await request.post('/file/fileinfo/upload', fd, {
      headers: { 'Content-Type': 'multipart/form-data' }
    })
    const fileId = resp.data?.id || resp.data?.data?.id
    if (!fileId) {
      ElMessage.error('上传失败：未获取文件ID')
      return
    }
    // 存储头像预览地址到用户头像字段（通用图片预览接口）
    formData.avatarUrl = `/api/file/fileinfo/preview/${fileId}`
    ElMessage.success('头像上传成功')
  } catch (e: any) {
    console.error('头像上传失败:', e)
    ElMessage.error(e?.message || '头像上传失败')
  }
}

// 表单取消
const handleCancel = () => {
  formVisible.value = false
  if (userFormRef.value) {
    userFormRef.value.resetFields()
  }
}

// 表单验证规则
const formRules: FormRules = {
  username: [
    { required: true, message: '请输入用户名', trigger: 'blur' },
    { min: 2, max: 50, message: '用户名长度在 2 到 50 个字符', trigger: 'blur' }
  ],
  password: [
    { required: !isEdit.value, message: '请输入密码', trigger: 'blur' },
    { min: 6, max: 20, message: '密码长度在 6 到 20 个字符', trigger: 'blur' }
  ],
  email: [
    { type: 'email', message: '请输入正确的邮箱地址', trigger: 'blur' }
  ]
}

// 角色分配相关方法
const handleAssignRole = async (row: UserDTO) => {
  try {
    currentUser.value = row
    roleDialogVisible.value = true

    // 加载可用角色和用户当前角色
    await Promise.all([
      loadAvailableRoles(),
      loadUserCurrentRoles(row.userId!)
    ])

  } catch (error) {
    ElMessage.error('加载角色信息失败')
    console.error('加载角色信息失败:', error)
  }
}

const loadAvailableRoles = async () => {
  try {
    const response = await roleApi.queryRoles({ current: 1, size: 1000 })
    availableRoles.value = Array.isArray(response.data?.data) ? response.data.data : []
  } catch (error) {
    console.error('加载可用角色失败:', error)
    ElMessage.error('加载可用角色失败')
  }
}

const loadUserCurrentRoles = async (userId: string) => {
  try {
    const response = await userRoleApi.getUserRoles(userId)
    userCurrentRoles.value = Array.isArray(response.data) ? response.data : []
    selectedRoleIds.value = [...userCurrentRoles.value]
  } catch (error) {
    console.error('加载用户当前角色失败:', error)
    ElMessage.error('加载用户当前角色失败')
  }
}

const selectAllRoles = () => {
  selectedRoleIds.value = availableRoles.value.map(role => role.roleId || role.id || '')
}

const clearAllRoles = () => {
  selectedRoleIds.value = []
}

const removeRole = (roleId: string) => {
  const index = selectedRoleIds.value.indexOf(roleId)
  if (index > -1) {
    selectedRoleIds.value.splice(index, 1)
  }
}

const getRoleName = (roleId: string) => {
  const role = availableRoles.value.find(r => (r.roleId || r.id) === roleId)
  return role ? (role.roleName || role.name) : roleId
}

const handleSaveRoles = async () => {
  if (!currentUser.value?.userId) {
    ElMessage.error('用户信息错误')
    return
  }

  try {
    roleLoading.value = true

    // 使用同步角色API，先清除再分配
    await userRoleApi.syncRoles(currentUser.value.userId, selectedRoleIds.value)

    ElMessage.success('角色分配成功')
    roleDialogVisible.value = false

    // 刷新用户列表
    getList()

  } catch (error: any) {
    console.error('分配角色失败:', error)
    ElMessage.error(error?.message || '分配角色失败')
  } finally {
    roleLoading.value = false
  }
}


// 头像加载错误处理
const handleAvatarError = (event: Event) => {
  const target = event.target as HTMLImageElement
  target.src = `https://api.dicebear.com/7.x/initials/svg?seed=User`
}

// 生命周期
onMounted(() => {
  getList()
})
</script>

<style lang="scss" scoped>
// 所有样式已迁移到模块化样式文件中：
// - 工具类样式 → src/styles/utility.scss
// - 角色选择样式 → src/styles/system-module.scss
// - 文本样式 → src/styles/utility.scss

// 如有组件特定的样式需求，可在此添加
</style>
